package com.neulogistics.contrib.warehouse.api.application.command.handler;

import com.blackto.lib.mediat.core.IMediator;
import com.blackto.lib.mediat.unicast.IRequestHandler;
import com.neulogistics.contrib.warehouse.api.application.command.*;
import com.neulogistics.contrib.warehouse.api.application.integrationevent.publish.PickUpOutboundIntegrationEvent;
import com.neulogistics.contrib.warehouse.api.application.integrationevent.WarehouseIntegrationEventService;
import com.neulogistics.contrib.warehouse.api.application.integrationevent.publish.CenterReturnOutboundIntegrationEvent;
import com.neulogistics.contrib.warehouse.api.application.integrationevent.publish.TransferOutboundIntegrationEvent;
import com.neulogistics.contrib.warehouse.api.application.rpc.IWarehouseRPC;
import com.neulogistics.contrib.warehouse.api.service.ThreadLocalService;
import com.neulogistics.contrib.warehouse.domain.exception.WarehouseDomainException;
import com.neulogistics.contrib.warehouse.domain.model.aggregate.CirculationOrder;
import com.neulogistics.contrib.warehouse.domain.model.aggregate.Inventory;
import com.neulogistics.contrib.warehouse.domain.model.aggregate.Warehouse;
import com.neulogistics.contrib.warehouse.domain.model.enumeration.CirculationDetail;
import com.neulogistics.contrib.warehouse.domain.model.enumeration.CirculationStatus;
import com.neulogistics.contrib.warehouse.domain.model.enumeration.CirculationType;
import com.neulogistics.contrib.warehouse.domain.model.enumeration.WarehouseLevel;
import com.neulogistics.contrib.warehouse.domain.model.valueobject.GoodsItem;
import com.neulogistics.contrib.warehouse.domain.repository.ICirculationOrderRepository;
import com.neulogistics.contrib.warehouse.domain.repository.IInventoryRepository;
import com.neulogistics.contrib.warehouse.domain.repository.IWarehouseRepository;
import com.neulogistics.infrastructure.cache.idservice.RedisIdUtil;
import com.neulogistics.infrastructure.common.annotation.ProduceEvent;
import com.neulogistics.infrastructure.common.serviceresult.BaseResponse;
import com.neulogistics.infrastructure.common.serviceresult.ErrorCode;
import com.neulogistics.infrastructure.common.serviceresult.ResultUtils;
import com.neulogistics.infrastructure.integrationeventlog.model.IntegrationEventConstant;
import org.redisson.api.RLock;
import org.redisson.api.RedissonClient;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Component;
import org.springframework.transaction.TransactionStatus;
import org.springframework.transaction.support.TransactionCallbackWithoutResult;
import org.springframework.transaction.support.TransactionTemplate;

import javax.annotation.Resource;

@Component
public class OutboundCommandHandler implements IRequestHandler<OutboundCommand, BaseResponse<Boolean>> {
    @Resource
    ICirculationOrderRepository circulationOrderRepository;

    @Resource
    IMediator mediator;

    @Override
    @ProduceEvent
    public BaseResponse<Boolean> handle(OutboundCommand command) throws WarehouseDomainException {
        // 根据出库单id查询对应实体
        CirculationOrder circulationOrder = circulationOrderRepository.findById(command.getCirculationId());

        //校验出库单状态
        circulationOrder.checkCirculationTypeAndDetail(CirculationType.Outbound);

        Boolean result = Boolean.FALSE;
        CirculationDetail circulationDetail = circulationOrder.getCirculationDetail();
        // 调拨出库
        if(circulationDetail == CirculationDetail.Transfer_Outbound){
            TransferOutboundCommand transferOutboundCommand =
                    new TransferOutboundCommand(command.circulationId, command.warehouseId);

            Boolean success = mediator.send(transferOutboundCommand);
            result = success == null ?
                    Boolean.FALSE : success;
        }
        // 退货出库
        else if(circulationDetail == CirculationDetail.Return_Outbound){
            ReturnOutboundCommand returnOutboundCommand =
                    new ReturnOutboundCommand(command.circulationId, command.warehouseId);

            Boolean success = mediator.send(returnOutboundCommand);
            result = success == null ?
                    Boolean.FALSE : success;
        }
        // 采购出库
        else if(circulationDetail == CirculationDetail.Pick_Up_Outbound){
            PickUpOutboundCommand pickUpOutboundCommand =
                    new PickUpOutboundCommand(command.circulationId, command.warehouseId);

            Boolean success = mediator.send(pickUpOutboundCommand);
            result = success == null ?
                    Boolean.FALSE : success;
        }
        return ResultUtils.success(result);
    }
}
